package com.guodi.map.utils;

import com.guodi.common.constant.StatusCode;
import com.guodi.core.minio.util.MinioUtil;
import com.guodi.core.tool.api.R;
import io.swagger.annotations.Api;
import io.swagger.annotations.ApiImplicitParam;
import io.swagger.annotations.ApiImplicitParams;
import io.swagger.annotations.ApiOperation;
import org.apache.any23.encoding.TikaEncodingDetector;
import org.apache.commons.lang.StringUtils;
import org.apache.poi.hssf.usermodel.HSSFWorkbook;
import org.apache.poi.ss.usermodel.Sheet;
import org.apache.poi.ss.usermodel.Workbook;
import org.apache.poi.xssf.usermodel.XSSFWorkbook;
import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;

import java.io.*;
import java.nio.charset.Charset;
import java.util.ArrayList;
import java.util.List;

/**
 * @描述：文件操作工具类
 * @作者: 戴伙进
 * @日期: 2020/5/21 20:51
 */
@RestController
@RequestMapping("/FileUtil")
@Api(value = "API - FileUtil", description = "下载工具类")
public class FileUtil {


    @PostMapping("/getHtmlFromDfs")
    @ApiOperation(value = "将txt和Excel文件转成html")
    @ApiImplicitParams({
            @ApiImplicitParam(name = "fileId", value = "文件id, 例如 group1/M00/00/00/CgABPl_9k_yAa9tuAANxrbL9GFU053.txt", required = true,
                    dataType = "string", paramType = "query",example = "group1/M00/00/00/CgABPl_9k_yAa9tuAANxrbL9GFU053.txt")
    })
    public R getHtmlFromDfs(String fileId) throws Exception {
        if (StringUtils.isBlank(fileId)) {
            return R.fail(StatusCode.ERROR_CODE_40005, "文件路径不能为空");
        }
        if (!fileId.endsWith("txt") && !fileId.endsWith("xlsx") && !fileId.endsWith("xls")) {
            return R.fail(StatusCode.ERROR_CODE_40005, "目前只能处理txt和Excel格式文件");
        }
        // 下载文件
        InputStream input = MinioUtil.download(fileId);
        ByteArrayOutputStream baos = cloneInputStream(input);
        // 打开两个新的输入流
        InputStream stream1 = new ByteArrayInputStream(baos.toByteArray());
        InputStream stream2 = new ByteArrayInputStream(baos.toByteArray());
        if (input == null){
            return R.fail(StatusCode.ERROR_CODE_40005, "文件不存在");
        }
        if (fileId.toLowerCase().endsWith(".txt")) {
            StringBuilder sb = new StringBuilder();
            String line;
            if(guessCharset(stream1).name().equals("UTF-8")){
                BufferedReader br = new BufferedReader(new InputStreamReader(stream2,"utf-8"));
                while ((line = br.readLine()) != null) {
                    sb.append(line + "</br>");
                }
            }else {
                BufferedReader br = new BufferedReader(new InputStreamReader(stream2,"GBK"));
                while ((line = br.readLine()) != null) {
                    sb.append(line + "</br>");
                }
            }
            String str = sb.toString();
            str = str.replaceAll(" ", "&nbsp;");
            str = str.replaceAll("\t", "&nbsp;&nbsp;&nbsp;&nbsp;");
            return R.data(str);
        }
        boolean isE2007 = false;
        // 判断是否是excel2007格式
        if (fileId.toLowerCase().endsWith(".xlsx")) {
            isE2007 = true;
        }
        List<List<String>> lists = new ArrayList<>();
        try {
            Workbook wb;
            // 根据文件格式(2003或者2007)来初始化
            if (isE2007) {
                wb = new XSSFWorkbook(input);
            } else {
                wb = new HSSFWorkbook(input);
            }
            // 获取第一个表单
            Sheet sheet = wb.getSheetAt(0);
            lists = ReadExcelUtil.shteetToList(sheet);
        } catch (Exception e) {
            e.printStackTrace();
        } finally {
            if (input != null) {
                input.close();
                stream1.close();
                stream2.close();
            }
        }
        return R.data(lists);
    }


    /**
    * @描述: 判断流的编码格式，不能百分之百判断正确
    * @入参:
    * @出参:
    * @作者: 代鹏刚
    * @日期: 2021/5/17 20:26
    **/
    public static Charset guessCharset(InputStream is) {
        try {
            return Charset.forName(new TikaEncodingDetector().guessEncoding(is));
        }catch (Exception e){
            e.printStackTrace();
        }
        return null;
    }

    private static ByteArrayOutputStream cloneInputStream(InputStream input) {
        try {
            ByteArrayOutputStream baos = new ByteArrayOutputStream();
            byte[] buffer = new byte[1024];
            int len;
            while ((len = input.read(buffer)) > -1) {
                baos.write(buffer, 0, len);
            }
            baos.flush();
            return baos;
        } catch (IOException e) {
            e.printStackTrace();
            return null;
        }
    }



}
